package com.monitor.service.impl;

import com.github.pagehelper.PageHelper;
import com.monitor.common.DateUtil;
import com.monitor.common.page.PageBean;
import com.monitor.common.response.CodeMsg;
import com.monitor.common.response.ResponseFactory;
import com.monitor.common.response.Result;
import com.monitor.dao.MonitorBakInfoDao;
import com.monitor.dao.MonitorBakInfoMapper;
import com.monitor.dao.MonitorInfoDao;
import com.monitor.dao.MonitorInfoMapper;
import com.monitor.pojo.MonitorBakInfo;
import com.monitor.pojo.MonitorInfo;
import com.monitor.service.MonitorService;
import com.monitor.vo.*;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.util.Date;
import java.util.List;

/**
 * @ClassName MonitorServiceImpl
 * @Package com.monitor.service.impl
 * @Description 报警监控业务处理具体实现
 * @Author zhixingbai
 * @Create 2018/10/1114:02
 */
@Service
public class MonitorServiceImpl implements MonitorService {

    private final Logger logger = LoggerFactory.getLogger(this.getClass());

    @Autowired
    MonitorInfoMapper monitorInfoMapper;
    @Autowired
    MonitorInfoDao monitorInfoDao;
    @Autowired
    MonitorBakInfoDao monitorBakInfoDao;

    @Autowired
    MonitorBakInfoMapper monitorBakInfoMapper;

    @Override
    public synchronized Result reqMonitor(MonitorReqVo[] reqVos) {
        for (MonitorReqVo reqVo : reqVos) {
            int exitsCount=monitorInfoDao.selectCount(reqVo.getAccount());
            if(exitsCount>0){
                MonitorInfo data = new MonitorInfo();
                BeanUtils.copyProperties(reqVo, data);
                data.setCreateTime(new Date());
                data.setUpdateTime(new Date());
                long startTime = System.currentTimeMillis();
                monitorInfoDao.updateByAccountAndType(data);
                logger.info("单笔更新耗时:{}", System.currentTimeMillis() - startTime);
            }
        }
        return ResponseFactory.build();
    }

    @Override
    public Result retMonitor(MonitorRetVo retVo) {
        //延迟5秒更新
        try {
            Thread.sleep(1000);
        } catch (InterruptedException e) {
            e.printStackTrace();
        }
        MonitorInfo data = monitorInfoDao.selectByAccount(retVo.getAccount(), retVo.getType());
        if (data == null) {
            logger.info("请求的账号不存在，账号:{},类型：{}", retVo.getAccount(), retVo.getType());
            return ResponseFactory.build(CodeMsg.ACCOUNT_NOT_EXITS);
        }
        logger.info("请求的账号存在，更新数据,账号:{},类型：{}", retVo.getAccount(), retVo.getType());
        data.setUpdateTime(new Date());
        data.setRetMsg(retVo.getRetMsg());
        data.setAccount(retVo.getAccount());
        data.setRetStatus(retVo.getRetStatus());
        data.setRetTime(retVo.getRetTime());
        int flag = monitorInfoDao.updateByVersion(data);
        if (flag <= 0) {
            logger.info("乐观锁更新失败:{},版本号：{}", data.getAccount(), data.getVersion());
        }
        saveBakInfo(data);
        return ResponseFactory.build();
    }

    @Override
    public PageBean<MonitorInfo> selectMonitorList(MonitorVo reqVo) {
        PageHelper.startPage(reqVo.getPageNum(), reqVo.getPageSize());
        List<MonitorInfo> list = monitorInfoDao.selectMonitorList(reqVo);
        for (MonitorInfo data : list) {
            CountVo countVo = monitorBakInfoDao.selectCount(data.getAccount(), data.getType());
            data.setFaileCount(countVo.getFaileCount());
            data.setInvalidCount(countVo.getInvalidCount());
            data.setValidCount(countVo.getValidCount());
        }
        return new PageBean<>(list);
    }

    @Override
    public PageBean<MonitorBakInfo> selectBakList(MonitorVo reqVo) {
        PageHelper.startPage(reqVo.getPageNum(), reqVo.getPageSize());
        List<MonitorBakInfo> list = monitorBakInfoDao.selectBakList(reqVo);
        return new PageBean<>(list);
    }

    @Override
    public List<MonitorInfo> selectMonitors(String ids) {
        return monitorInfoDao.selectMonitors(ids);
    }

    @Override
    public Result delBak(Integer delDate) {
        int flag = monitorBakInfoDao.delBak(delDate);
        return ResponseFactory.build();
    }

    @Override
    public Result setCostTime(MonitorEditReq editReq) {
        MonitorInfo monitorInfo=new MonitorInfo();
        BeanUtils.copyProperties(editReq,monitorInfo);
        int flag;
        if(editReq.getId()==null){
            monitorInfo.setCreateTime(new Date());
            flag=monitorInfoMapper.insertSelective(monitorInfo);
        }else{
            monitorInfo.setUpdateTime(new Date());
            flag=monitorInfoMapper.updateByPrimaryKeySelective(monitorInfo);
        }
        if(flag<=0){
            return ResponseFactory.build(CodeMsg.ERROR,"更新失敗");
        }
        return ResponseFactory.build();
    }

    @Override
    public Result setTypeTime(MonitorEditReq editReq) {
        int flag=monitorInfoDao.updateByType(editReq);
        if(flag<=0){
            return ResponseFactory.build(CodeMsg.ERROR,"更新失敗");
        }
        return ResponseFactory.build();
    }

    @Override
    public Result delMonitor(Integer id) {
        MonitorInfo monitorInfo=monitorInfoMapper.selectByPrimaryKey(id);
        if(monitorInfo==null){
            return ResponseFactory.build(CodeMsg.ACCOUNT_NOT_EXITS);
        }
        int delFlag=monitorInfoDao.delMonitorById(id);
        if(delFlag>0){
            monitorBakInfoDao.delByAccount(monitorInfo.getAccount(),monitorInfo.getType());
        }
        return ResponseFactory.build();
    }

    @Override
    public Result editWarning(Integer id, String isWarning) {
        MonitorInfo info=new MonitorInfo();
        info.setId(id);
        info.setIsWarning(isWarning);
        monitorInfoMapper.updateByPrimaryKeySelective(info);
        return ResponseFactory.build();
    }

    /**
     * 保存备份数据
     *
     * @param data
     */
    private void saveBakInfo(MonitorInfo data) {
        //插入备份表数据
        MonitorBakInfo bakInfo = new MonitorBakInfo();
        bakInfo.setAccount(data.getAccount());
        bakInfo.setBankName(data.getBankName());
        bakInfo.setBizId(data.getBizId());
        bakInfo.setCreateTime(data.getCreateTime());
        bakInfo.setIfCode(data.getIfCode());
        bakInfo.setReqTime(data.getReqTime());
        bakInfo.setRetTime(data.getRetTime());
        bakInfo.setRetMsg(data.getRetMsg());
        bakInfo.setRetStatus(data.getRetStatus());
        bakInfo.setType(data.getType());
        bakInfo.setAccountType(data.getAccountType());
        bakInfo.setUpdateTime(data.getUpdateTime());
        monitorBakInfoMapper.insertSelective(bakInfo);
    }
}
